﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using MaxLeaf.Platform.DataContract;
using CommonsLib.DB;
using MaxLeaf.Platform.DALImplementation;
using MaxLeaf.Platform.Functions;
using CommonsLib.Utility;
using MaxLeaf.Platform.Commons;
using MaxLeaf.Platform.Contract;
using System.Transactions;
using CommonsLib.Utility;
using CommonsLib.Settings;

namespace MaxLeaf.Platform.BLLImplementation
{
    public class imStoresOutputProcessor :   IStoresOutputProcess
    {




        public imOthersOutputHdrDataModel Post(int intEnterUserId, int intStoresOutputHdrID, List<int> lstStoresOutputDtlKeys, string strRemark)
        {
 
            imStoresOutputHdrBLL bllStoresOutputHdr = new imStoresOutputHdrBLL();
            imStoresOutputDtlBLL bllStoresOutputDtl = new imStoresOutputDtlBLL(); ;
            if (lstStoresOutputDtlKeys == null || lstStoresOutputDtlKeys.Count == 0)
            {
                //得到unposted dtl
                lstStoresOutputDtlKeys = bllStoresOutputDtl.GetUnpostKeys(intStoresOutputHdrID);
                if (lstStoresOutputDtlKeys == null || lstStoresOutputDtlKeys.Count == 0)
                {
                    throw new MaxLeafException(string.Format(Const.MSG_NoDataToPost, intStoresOutputHdrID));
                }
            }

            imStoresOutputHdrDataModel modelStoresOutputHdr = new imStoresOutputHdrDataModel();
            modelStoresOutputHdr = (imStoresOutputHdrDataModel)bllStoresOutputHdr.Select(modelStoresOutputHdr, intStoresOutputHdrID);
            if (modelStoresOutputHdr.Posted)
            {
                throw new MaxLeafException(string.Format(Const.MSG_NoDataToPost, intStoresOutputHdrID));
            }

            BaseBLL bllOthersOutputHdr = BaseBLL.GetDataModelBLL("imOthersOutputHdrDataModel");
            imOthersOutputDtlBLL bllOthersOutputDtl = new imOthersOutputDtlBLL();

            //插入imOthersOutputHdr.Finterid
            imOthersOutputHdrDataModel modelOthersOutputHdr = Post_InitHdr(bllOthersOutputHdr, modelStoresOutputHdr, intEnterUserId,  strRemark);

            List<imOthersOutputDtlDataModel> lstOrderDtl = new List<imOthersOutputDtlDataModel>();
            for (int i = 0; i < lstStoresOutputDtlKeys.Count; i++)
            {

                imStoresOutputDtlDataModel modelStoresOutputDtl = new imStoresOutputDtlDataModel();
                modelStoresOutputDtl = (imStoresOutputDtlDataModel)bllStoresOutputDtl.Select(modelStoresOutputDtl, lstStoresOutputDtlKeys[i]);
                //插入imOthersOutputHdr.Finterid
                lstOrderDtl.Add(Post_InitDtl(bllOthersOutputDtl, modelOthersOutputHdr.Key, modelStoresOutputDtl));

            }

            using (System.Transactions.TransactionScope ts = DataFunc.CreateTransactionScope())
            {
                using (DBAccess dbConOrder = new DBAccess(DataFunc.GetConnectionInfo(Const.DB_SCPSEOrder)))
                {
                    try
                    {
                        //dbConOrder.BeginTrans();
                        if (!bllStoresOutputHdr.CurrentBRL.CanPost(dbConOrder, bllStoresOutputHdr.CurrentDAL, "imStoresOutputHdr", "FinterId", intStoresOutputHdrID))
                        {
                            throw new MaxLeafException(string.Format(Const.MSG_NoDataToPost, intStoresOutputHdrID));
                        }
                        //保存 imOthersOutputHdr 其他数据
                        modelOthersOutputHdr = (imOthersOutputHdrDataModel)bllOthersOutputHdr.Update(dbConOrder, modelOthersOutputHdr);



                        for (int i = 0; i < lstStoresOutputDtlKeys.Count; i++)
                        {
                            if (bllStoresOutputDtl.CurrentBRL.CanPost(dbConOrder, bllStoresOutputDtl.CurrentDAL, "imStoresOutputDtl", "DtlId", lstStoresOutputDtlKeys[i]))
                            {
                                //保存 imOthersOutputDtl 其他数据
                                lstOrderDtl[i] = (imOthersOutputDtlDataModel)bllOthersOutputDtl.Update(dbConOrder, lstOrderDtl[i]);
                                //写入来源 StoresOutputDtl key
                                bllOthersOutputDtl.SetStoresOutputDtlId(dbConOrder, lstOrderDtl[i].Key, intStoresOutputHdrID, lstStoresOutputDtlKeys[i]);

                                //设置StoresOutputDtl Post标志
                                bllStoresOutputDtl.SetPosted(dbConOrder, lstStoresOutputDtlKeys[i], lstOrderDtl[i].ForeignKey, lstOrderDtl[i].Key);
                            }

                        }
                        //设置StoresOutputHdr Post标志
                        bllStoresOutputHdr.SetPosted(dbConOrder, intStoresOutputHdrID);

                        //dbConOrder.CommitTrans();
                    }
                    catch(Exception ex)
                    {
                        //dbConOrder.RollbackTrans();
                        LogManager.Debug(ex.Message);
                        throw;
                    }
                }

                new OutputProcessor().AutoLocAppro(modelOthersOutputHdr);

                ts.Complete();
            }
            


            

             
            return modelOthersOutputHdr;

            
        }





        private imOthersOutputDtlDataModel Post_InitDtl(imOthersOutputDtlBLL bllOthersOutputDtl, int intForeignKey, imStoresOutputDtlDataModel modelStoresOutputDtl)
        {
            if (modelStoresOutputDtl.Qty.CompareTo(0d) <= 0)
            {
                throw new MaxLeafException("数量不能为0");
            }

            imOthersOutputDtlDataModel modelDtl = new imOthersOutputDtlDataModel(
                intForeignKey
                , modelStoresOutputDtl.ItemID
                , modelStoresOutputDtl.UnitID
                , modelStoresOutputDtl.Qty
                , modelStoresOutputDtl.Price
                , modelStoresOutputDtl.Subtotal * modelStoresOutputDtl.Qty / modelStoresOutputDtl.ReqQty
                 , modelStoresOutputDtl.Cost
                );

            return (imOthersOutputDtlDataModel)bllOthersOutputDtl.InsertFinterID(modelDtl);
        }

        private imOthersOutputHdrDataModel Post_InitHdr(BaseBLL bllOthersOutputHdr, imStoresOutputHdrDataModel modelStoresOutputHdr, int EnterUserID, string strRemark)
        {
            int DocType = new mOutputTypeBLL().GetStoresOutputTypeId(modelStoresOutputHdr.CompanyID);
            imOthersOutputHdrDataModel modelHdr = new imOthersOutputHdrDataModel(
                modelStoresOutputHdr.CompanyID
                , modelStoresOutputHdr.DepID
                ,DateTime.Now
                , DocType
                , modelStoresOutputHdr.ReqUserID
                , EnterUserID
                ,strRemark
               );
            return (imOthersOutputHdrDataModel)bllOthersOutputHdr.InsertFinterID(modelHdr);
        }


        public bool GeneratNewStoreOutFromStoreReq(DBAccess dbcon, imStoresReqHdrDataModel imOrigReqHdrModel)
        {
            imStoresOutputHdrDataModel imHdrModel = new imStoresOutputHdrDataModel();
            imHdrModel = GeneratNewStoreOutFromStoreReqHdr(dbcon, imOrigReqHdrModel);

            GeneratNewStoreOutFromStoreReqDtl(dbcon, imOrigReqHdrModel, imHdrModel.Key);
            return true;
        }

        private imStoresOutputHdrDataModel GeneratNewStoreOutFromStoreReqHdr(DBAccess dbcon, imStoresReqHdrDataModel imOrigReqHdrModel)
        {
            imStoresOutputHdrDataModel imOutModel = new imStoresOutputHdrDataModel();
            
            imStoresOutputHdrBLL imBLL = new imStoresOutputHdrBLL();
                        
            if (imOrigReqHdrModel.OrigFInterID > 0) //如果是总公司审核完下推的就，就用去找分公司的companyid
            {
                imOutModel.CompanyID = CvtFunc.ToInt(dbcon.GetValue("Select CompanyID From imStoresReqHdr Where FinterID='" + imOrigReqHdrModel.OrigFInterID + "'"));
            }
            else  //如果是分公司自己的，不是总公司审核完下推的就，就用自己的companyid
            {
                imOutModel.CompanyID = imOrigReqHdrModel.CompanyID;
            }
            imBLL.InsertFinterID(imOutModel);
            imOutModel.DepID = imOrigReqHdrModel.DepartID;
            imOutModel.DocDate = DateTime.Now;
            imOutModel.DocStatus = 0;
            imOutModel.ReqUserID = imOrigReqHdrModel.ReqUserID;
            imOutModel.EnterUserID = imOrigReqHdrModel.ReqUserID;

            return (imStoresOutputHdrDataModel)imBLL.Update(imOutModel);  
        }

        private bool GeneratNewStoreOutFromStoreReqDtl(DBAccess dbcon, imStoresReqHdrDataModel imOrigReqHdrModel,int intHdrFinterID)
        {
            imStoresOutputDtlDataModel imNewStoreOutDtl = new imStoresOutputDtlDataModel();

            imStoresReqDtlDataModel imDtlModel = new imStoresReqDtlDataModel();
            imStoresOutputDtlBLL imBLL = new imStoresOutputDtlBLL ();
            List<Object> imStoreReqDtl = (List<Object>)BaseBLL.GetDataModelBLL("imStoresReqDtlDataModel").SelectDtl(imDtlModel , imOrigReqHdrModel.Key );
            for (int i = 0; i <= imStoreReqDtl.Count-1; i++)
            {
                imStoresReqDtlDataModel imOrigStoreReqDtl = imStoreReqDtl[i] as imStoresReqDtlDataModel;
                if (imOrigStoreReqDtl.Is_Delete == true) continue;
                imNewStoreOutDtl =(imStoresOutputDtlDataModel)imBLL.InsertFinterID ( imNewStoreOutDtl);

                imNewStoreOutDtl.Cost = imOrigStoreReqDtl.Price;
                imNewStoreOutDtl.ForeignKey = intHdrFinterID;
                imNewStoreOutDtl.ItemID = imOrigStoreReqDtl.ItemID;                
                imNewStoreOutDtl.Price = imOrigStoreReqDtl.Price;
                imNewStoreOutDtl.Qty = imOrigStoreReqDtl.ReqQty;
                imNewStoreOutDtl.UnitID = imOrigStoreReqDtl.UnitID;
                imNewStoreOutDtl.OutputQty = 0;
                imNewStoreOutDtl.StoreReqDtlID = imOrigStoreReqDtl.Key;
                imNewStoreOutDtl.ReqQty = imOrigStoreReqDtl.ReqQty;
                imNewStoreOutDtl.Subtotal = imOrigStoreReqDtl.ReqQty*imOrigStoreReqDtl.Price;

                imNewStoreOutDtl = (imStoresOutputDtlDataModel)imBLL.Update(imNewStoreOutDtl);
            }
            return true;
        }


        public bool UnPost(int intOthersOutputHdrID)
        {


            imOthersOutputHdrBLL bllOthersOutputHdr = new imOthersOutputHdrBLL();
            imOthersOutputDtlBLL bllOthersOutputDtl = new imOthersOutputDtlBLL();

            imOthersOutputHdrDataModel modelOthersOutputHdr = (imOthersOutputHdrDataModel)bllOthersOutputHdr.Select(new imOthersOutputHdrDataModel(), intOthersOutputHdrID);
            if (modelOthersOutputHdr == null || modelOthersOutputHdr.Is_Delete || modelOthersOutputHdr.Posted)
            {
                throw new MaxLeafException(string.Format(Const.MSG_NoDataToUnPost, intOthersOutputHdrID));
            }

            List<int> lstOthersOutputDtlKeys = bllOthersOutputDtl.GetUnpostKeys(intOthersOutputHdrID);
            if (lstOthersOutputDtlKeys == null || lstOthersOutputDtlKeys.Count == 0)
            {
                throw new MaxLeafException(string.Format(Const.MSG_NoDataToUnPost, intOthersOutputHdrID));
            }

            imStoresOutputHdrBLL bllStoresOutputHdr = new imStoresOutputHdrBLL();
            imStoresOutputDtlBLL bllStoresOutputDtl = new imStoresOutputDtlBLL(); ;



            using (System.Transactions.TransactionScope ts = DataFunc.CreateTransactionScope())
            {
                using (DBAccess dbConOrder = new DBAccess(DataFunc.GetConnectionInfo(Const.DB_SCPSEOrder)))
                {
                    try
                    {
                        List<int> lstRecvHdrKeys = new List<int>();
                        imOthersOutputDtlDataModel modelOthersOutputDtl_tmp = new imOthersOutputDtlDataModel();
                        for (int i = 0; i < lstOthersOutputDtlKeys.Count; i++)
                        {
                            int intStoresOutputHdrId, intStoresOutputDtlId;
                            double dblRecvQty;
                            bllOthersOutputDtl.GetRecvData(dbConOrder, lstOthersOutputDtlKeys[i], out intStoresOutputHdrId, out intStoresOutputDtlId, out dblRecvQty);

                            bllStoresOutputDtl.SetUnPosted(dbConOrder, intStoresOutputHdrId, intStoresOutputDtlId, dblRecvQty);
                            bllOthersOutputDtl.SetUnRecv(dbConOrder, lstOthersOutputDtlKeys[i]);

                            if (!lstRecvHdrKeys.Contains(intStoresOutputHdrId))
                            {
                                lstRecvHdrKeys.Add(intStoresOutputHdrId);
                            }
                        }
                        for (int i = 0; i < lstRecvHdrKeys.Count; i++)
                        {
                            bllStoresOutputHdr.SetUnPosted(dbConOrder, lstRecvHdrKeys[i]);
                        }
                        bllOthersOutputHdr.SetUnRecv(dbConOrder, intOthersOutputHdrID);


                    }
                    catch
                    {

                        throw;
                    }
                }


                ts.Complete();
            }



            return true;
        }
    }
}
